package io.grpc.examples.helloworldtls.trust;

import java.security.InvalidAlgorithmParameterException;
import java.security.KeyStore;
import java.security.KeyStoreException;
import java.security.cert.CertificateException;
import java.security.cert.X509Certificate;

import javax.net.ssl.ManagerFactoryParameters;
import javax.net.ssl.TrustManager;
import javax.net.ssl.TrustManagerFactorySpi;
import javax.net.ssl.X509TrustManager;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

/**
 * 采用区块链进行证书校验。
 */
public class MyTrustManagerFactorySpi extends TrustManagerFactorySpi {

    private static final Logger log = LoggerFactory.getLogger(MyTrustManagerFactorySpi.class);

    private static final TrustManager BLOCKCHAIN_TRUST_MANAGER = new X509TrustManager() {

        @Override
        public X509Certificate[] getAcceptedIssuers() {
            System.out.println("获取证书");
            log.info("获取证书");
            return new X509Certificate[0];
        }

        @Override
        public void checkClientTrusted(X509Certificate[] chain, String authType) throws CertificateException {
            System.out.println("校验客户端证书，证书链长度=" + chain.length + "，认证类型=" + authType);
//            System.out.println(chain[0]);
            log.info("校验客户端证书，证书链长度={}，认证类型={}", chain.length, authType);
            log.info("认证通过");
        }

        @Override
        public void checkServerTrusted(X509Certificate[] chain, String authType) throws CertificateException {
            System.out.println("校验服务器证书，证书链长度=" + chain.length + "，认证类型=" + authType);
//            System.out.println(chain[0]);
            log.info("校验服务器证书，证书链长度={}，认证类型={}", chain.length, authType);
            log.info("认证通过");
        }

    };

    public static TrustManager[] getTrustManagers() {
        return new TrustManager[] { BLOCKCHAIN_TRUST_MANAGER };
    }

    @Override
    protected TrustManager[] engineGetTrustManagers() {
        return getTrustManagers();
    }

    @Override
    protected void engineInit(KeyStore keystore) throws KeyStoreException {
        // do nothing
        Elliptic.init();
    }

    @Override
    protected void engineInit(ManagerFactoryParameters managerFactoryParameters)
            throws InvalidAlgorithmParameterException {
        // do nothing
        Elliptic.init();
    }
}